package com.prd.service.impl;

import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.baomidou.mybatisplus.core.metadata.IPage;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import com.prd.dto.CustomerDTO;
import com.prd.dto.CustomerProjectDTO;
import com.prd.dto.CustomerRemarkDTO;
import com.prd.enums.CustomerRemarkEnum;
import com.prd.mapper.CustomerProjectMapper;
import com.prd.model.CustomerGuestDO;
import com.prd.model.CustomerProjectDO;
import com.prd.service.CustomerGuestService;
import com.prd.service.CustomerProjectService;
import com.prd.service.CustomerRemarkService;
import com.prd.service.CustomerService;
import com.prd.tools.CopyNonNullBeanUtils;
import com.prd.tools.DTOUtil;
import com.prd.util.JsonData;
import org.springframework.beans.BeanUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;

import javax.annotation.Resource;
import java.util.*;
import java.util.stream.Collectors;

/**
 * <p>
 * 客户-项目 服务实现类
 * </p>
 *
 * @author o1
 * @since 2023-11-24
 */
@Service("CustomerProjectService")
public class CustomerProjectServiceImpl extends ServiceImpl<CustomerProjectMapper, CustomerProjectDO> implements CustomerProjectService {

    @Autowired
    private CustomerProjectMapper projectMapper;

    @Resource(name = "CustomerService")
    private CustomerService customerService;
    @Resource(name = "CustomerGuestService")
    private CustomerGuestService guestService;
    @Resource(name = "CustomerRemarkService")
    private CustomerRemarkService remarkService;

    @Override
    public JsonData uAddSimple(CustomerProjectDTO customerProjectDTO) {
        String projectId = String.valueOf(customerProjectDTO.hashCode());
        LambdaQueryWrapper<CustomerProjectDO> lambdaQueryWrapper = new LambdaQueryWrapper<>();
        lambdaQueryWrapper.eq(CustomerProjectDO::getProjectId, projectId);
        lambdaQueryWrapper.eq(CustomerProjectDO::getCustomerNo, customerProjectDTO.getCustomerNo());
        CustomerProjectDO projectDO = projectMapper.selectOne(lambdaQueryWrapper);
        //不存在项目id
        if (projectDO == null) {
            customerProjectDTO.setProjectId(projectId);
            projectDO = new CustomerProjectDO();
            BeanUtils.copyProperties(customerProjectDTO, projectDO);
            projectDO.setProjectCreateDate(new Date());
            projectMapper.insert(projectDO);
            //项目分析id列表
            if (customerProjectDTO.getProjectAnalyzeList() != null && !customerProjectDTO.getProjectAnalyzeList().isEmpty()) {
                for (CustomerRemarkDTO proAnalyzeDTO : customerProjectDTO.getProjectAnalyzeList()) {
                    proAnalyzeDTO.setNo(projectId);
                    proAnalyzeDTO.setType(CustomerRemarkEnum.ProjectAnalyze.getCode());
                    remarkService.uAdd(proAnalyzeDTO);
                }
            }
            //项目需求id列表
            if (customerProjectDTO.getProjectRequirementsList() != null && !customerProjectDTO.getProjectRequirementsList().isEmpty()) {
                for (CustomerRemarkDTO reqRemarkDTO : customerProjectDTO.getProjectRequirementsList()) {
                    reqRemarkDTO.setNo(projectId);
                    reqRemarkDTO.setType(CustomerRemarkEnum.ProjectRequirementRemark.getCode());
                    remarkService.uAdd(reqRemarkDTO);
                }
            }
            //项目备注id列表
            if (customerProjectDTO.getProjectRemarkList() != null && !customerProjectDTO.getProjectRemarkList().isEmpty()) {
                for (CustomerRemarkDTO proRemarkDTO : customerProjectDTO.getProjectRemarkList()) {
                    proRemarkDTO.setNo(projectId);
                    proRemarkDTO.setType(CustomerRemarkEnum.ProjectRemark.getCode());
                    remarkService.uAdd(proRemarkDTO);
                }
            }
            //销售/业务-策略/方案id列表
            if (customerProjectDTO.getProjectStrategyList() != null && !customerProjectDTO.getProjectStrategyList().isEmpty()) {
                for (CustomerRemarkDTO proStrategyDTO : customerProjectDTO.getProjectStrategyList()) {
                    proStrategyDTO.setNo(projectId);
                    proStrategyDTO.setType(CustomerRemarkEnum.ProjectStrategy.getCode());
                    remarkService.uAdd(proStrategyDTO);
                }
            }
            //销售/业务-计划/实施id列表
            if (customerProjectDTO.getProjectPlanList() != null && !customerProjectDTO.getProjectPlanList().isEmpty()) {
                for (CustomerRemarkDTO proPlanDTO : customerProjectDTO.getProjectPlanList()) {
                    proPlanDTO.setNo(projectId);
                    proPlanDTO.setType(CustomerRemarkEnum.ProjectPlan.getCode());
                    remarkService.uAdd(proPlanDTO);
                }
            }
            return JsonData.buildSuccess(projectDO);
        }
        else {
            return JsonData.buildError("同个客户下已有相同项目");
        }
    }

    @Override
    public JsonData addSimple(CustomerProjectDO projectDO) {
        String projectId = String.valueOf(projectDO.hashCode());
        LambdaQueryWrapper<CustomerProjectDO> lambdaQueryWrapper = new LambdaQueryWrapper<>();
        lambdaQueryWrapper.eq(CustomerProjectDO::getProjectId, projectId);
        lambdaQueryWrapper.eq(CustomerProjectDO::getCustomerNo, projectDO.getCustomerNo());
        CustomerProjectDO projectDB = projectMapper.selectOne(lambdaQueryWrapper);
        //不存在项目id
        if (projectDB == null) {
            projectDO.setProjectId(projectId);
            projectDB = new CustomerProjectDO();
            BeanUtils.copyProperties(projectDO, projectDB);
            projectDB.setProjectCreateDate(new Date());
            projectMapper.insert(projectDB);
            return JsonData.buildSuccess(projectDB);
        }
        else {
            return JsonData.buildError("同个客户下已有相同项目");
        }
    }

    @Override
    public JsonData uUpdateAndAddSimple(CustomerProjectDTO customerProjectDTO) {
        String projectId = String.valueOf(customerProjectDTO.hashCode());
        LambdaQueryWrapper<CustomerProjectDO> lambdaQueryWrapper = new LambdaQueryWrapper<>();
        lambdaQueryWrapper.eq(CustomerProjectDO::getProjectId, projectId);
        lambdaQueryWrapper.eq(CustomerProjectDO::getCustomerNo, customerProjectDTO.getCustomerNo());
        CustomerProjectDO projectDO = projectMapper.selectOne(lambdaQueryWrapper);
        //不存在项目id
        if (projectDO == null) {
            return uAddSimple(customerProjectDTO);
        }else {
            CopyNonNullBeanUtils.copyProperties(projectDO, customerProjectDTO);
            //项目分析id列表
            if (customerProjectDTO.getProjectAnalyzeList() != null && !customerProjectDTO.getProjectAnalyzeList().isEmpty()) {
                for (CustomerRemarkDTO proAnalyzeDTO : customerProjectDTO.getProjectAnalyzeList()) {
                    proAnalyzeDTO.setNo(projectId);
                    proAnalyzeDTO.setType(CustomerRemarkEnum.ProjectAnalyze.getCode());
                    remarkService.uUpdateAndAdd(proAnalyzeDTO);
                }
            }
            //项目需求id列表
            if (customerProjectDTO.getProjectRequirementsList() != null && !customerProjectDTO.getProjectRequirementsList().isEmpty()) {
                for (CustomerRemarkDTO reqRemarkDTO : customerProjectDTO.getProjectRequirementsList()) {
                    reqRemarkDTO.setNo(projectId);
                    reqRemarkDTO.setType(CustomerRemarkEnum.ProjectRequirementRemark.getCode());
                    remarkService.uUpdateAndAdd(reqRemarkDTO);
                }
            }
            //项目备注id列表
            if (customerProjectDTO.getProjectRemarkList() != null && !customerProjectDTO.getProjectRemarkList().isEmpty()) {
                for (CustomerRemarkDTO proRemarkDTO : customerProjectDTO.getProjectRemarkList()) {
                    proRemarkDTO.setNo(projectId);
                    proRemarkDTO.setType(CustomerRemarkEnum.ProjectRemark.getCode());
                    remarkService.uAdd(proRemarkDTO);
                }
            }
            //销售/业务-策略/方案id列表
            if (customerProjectDTO.getProjectStrategyList() != null && !customerProjectDTO.getProjectStrategyList().isEmpty()) {
                for (CustomerRemarkDTO proStrategyDTO : customerProjectDTO.getProjectStrategyList()) {
                    proStrategyDTO.setNo(projectId);
                    proStrategyDTO.setType(CustomerRemarkEnum.ProjectStrategy.getCode());
                    remarkService.uUpdateAndAdd(proStrategyDTO);
                }
            }
            //销售/业务-计划/实施id列表
            if (customerProjectDTO.getProjectPlanList() != null && !customerProjectDTO.getProjectPlanList().isEmpty()) {
                for (CustomerRemarkDTO proPlanDTO : customerProjectDTO.getProjectPlanList()) {
                    proPlanDTO.setNo(projectId);
                    proPlanDTO.setType(CustomerRemarkEnum.ProjectPlan.getCode());
                    remarkService.uUpdateAndAdd(proPlanDTO);
                }
            }
            return JsonData.buildSuccess(projectDO);
        }
    }

    @Override
    public JsonData uSearch(String customerNo) {
        List<CustomerProjectDTO> projectDOList = searchForList(customerNo);
        if (projectDOList.isEmpty())
            return JsonData.buildError("没有对应项目");
        return JsonData.buildSuccess(projectDOList);
    }

    @Override
    public List<CustomerProjectDTO> searchForList(String customerNo) {
        List<CustomerProjectDTO> projectDTOList = new ArrayList<>();
        if (customerNo == null)
            return projectDTOList;
        LambdaQueryWrapper<CustomerProjectDO> lambdaQueryWrapper = new LambdaQueryWrapper<>();
        lambdaQueryWrapper.eq(CustomerProjectDO::getCustomerNo, customerNo);
        List<CustomerProjectDO> projectDOList = projectMapper.selectList(lambdaQueryWrapper);
        for (CustomerProjectDO projectDO: projectDOList) {
            CustomerProjectDTO projectDTO = new CustomerProjectDTO();
            BeanUtils.copyProperties(projectDO, projectDTO);
            projectDTO.setProjectAnalyzeList(remarkService.uSearchForList(projectDO.getProjectId(), CustomerRemarkEnum.ProjectAnalyze.getCode()));
            projectDTO.setProjectRequirementsList(remarkService.uSearchForList(projectDO.getProjectId(), CustomerRemarkEnum.ProjectRequirementRemark.getCode()));
            projectDTO.setProjectRemarkList(remarkService.uSearchForList(projectDO.getProjectId(), CustomerRemarkEnum.ProjectRemark.getCode()));
            projectDTO.setProjectStrategyList(remarkService.uSearchForList(projectDO.getProjectId(), CustomerRemarkEnum.ProjectStrategy.getCode()));
            projectDTO.setProjectPlanList(remarkService.uSearchForList(projectDO.getProjectId(), CustomerRemarkEnum.ProjectPlan.getCode()));
            projectDTOList.add(projectDTO);
        }
        return projectDTOList;
    }

    @Override
    public JsonData uAddAndUpdate(CustomerProjectDTO projectDTO) {
        if (projectDTO.getProjectId() == null)
            return JsonData.buildError("请检查projectId参数");

//        List<CustomerRemarkDTO> projectAnalyzeList = remarkService.uSearchForList(projectDTO.getProjectId(), CustomerRemarkEnum.ProjectAnalyze.getCode());
//        List<CustomerRemarkDTO> projectRequirementsList = remarkService.uSearchForList(projectDTO.getProjectId(), CustomerRemarkEnum.ProjectRequirementRemark.getCode());
//        List<CustomerRemarkDTO> projectRemarkList = remarkService.uSearchForList(projectDTO.getProjectId(), CustomerRemarkEnum.ProjectRemark.getCode());
//        List<CustomerRemarkDTO> projectStrategyList = remarkService.uSearchForList(projectDTO.getProjectId(), CustomerRemarkEnum.ProjectStrategy.getCode());
//        List<CustomerRemarkDTO> projectPlanList = remarkService.uSearchForList(projectDTO.getProjectId(), CustomerRemarkEnum.ProjectPlan.getCode());
//
//        HashMap<String, Object> otherParam = new HashMap<String, Object>();
//        otherParam.put("projectId", projectDTO.getProjectId());
//
//        otherParam.put("code", CustomerRemarkEnum.ProjectAnalyze.getCode());
//        DTOUtil.compareDBAndDOList(projectAnalyzeList, projectDTO.getProjectAnalyzeList(), remarkService, otherParam);
//
//        otherParam.put("code", CustomerRemarkEnum.ProjectRequirementRemark.getCode());
//        DTOUtil.compareDBAndDOList(projectRequirementsList, projectDTO.getProjectRequirementsList(), remarkService, otherParam);
//
//        otherParam.put("code", CustomerRemarkEnum.ProjectRemark.getCode());
//        DTOUtil.compareDBAndDOList(projectRemarkList, projectDTO.getProjectRemarkList(), remarkService, otherParam);
//
//        otherParam.put("code", CustomerRemarkEnum.ProjectStrategy.getCode());
//        DTOUtil.compareDBAndDOList(projectStrategyList, projectDTO.getProjectStrategyList(), remarkService, otherParam);
//
//        otherParam.put("code", CustomerRemarkEnum.ProjectPlan.getCode());
//        DTOUtil.compareDBAndDOList(projectPlanList, projectDTO.getProjectPlanList(), remarkService, otherParam);

        return update(DTOUtil.projectDtoToDO(projectDTO));
    }

    @Override
    public JsonData update(CustomerProjectDO projectDO) {
        LambdaQueryWrapper<CustomerProjectDO> wrapper = new LambdaQueryWrapper<>();
        wrapper.eq(CustomerProjectDO::getProjectId, projectDO.getProjectId());
        CustomerProjectDO projectDB = projectMapper.selectOne(wrapper);
        if (projectDB == null)
            return JsonData.buildError("没有对应项目");
        CopyNonNullBeanUtils.copyProperties(projectDO, projectDB);
        projectMapper.update(projectDO, wrapper);
        return JsonData.buildSuccess(projectDO);
    }

    @Override
    public Map<String, Object> uCountProjectBusStatus() {
        Map<String, Object> map = new HashMap<>(3);
        LambdaQueryWrapper<CustomerProjectDO> wrapper = new LambdaQueryWrapper<>();
        //客户类型: 项目类1，供应链类2，服务类3，渠道类4，消费类5
        int total_record = projectMapper.selectCount(wrapper);
        map.put("total_record", total_record);
        int project_record = projectMapper.selectCount(wrapper.eq(CustomerProjectDO::getProjectBusStatus, 1));
        map.put("working_record", project_record);
        int support_record = projectMapper.selectCount(wrapper.eq(CustomerProjectDO::getProjectBusStatus, 2));
        map.put("done_record", support_record);
        int service_record = projectMapper.selectCount(wrapper.eq(CustomerProjectDO::getProjectBusStatus, 3));
        map.put("failed_record", service_record);
        return map;
    }

    @Override
    public JsonData uChangeProjectBusStatus(CustomerProjectDTO projectDTO) {
        if (projectDTO.getProjectId() == null || projectDTO.getProjectBusStatus() == -1)
            return JsonData.buildError("请检查projectId/projectBusStatus参数");
        LambdaQueryWrapper<CustomerProjectDO> wrapper = new LambdaQueryWrapper<>();
        wrapper.eq(CustomerProjectDO::getProjectId, projectDTO.getProjectId());
        CustomerProjectDO projectDO = projectMapper.selectOne(wrapper);
        if (projectDO == null)
            return JsonData.buildError("没有对应项目");
        //提交项目相关操作备注
        CustomerRemarkDTO remarkDTO = projectDTO.getProjectResult();
        if (remarkDTO != null) {
            remarkDTO.setNo(projectDTO.getProjectId());
            int type = 0;
            switch (projectDTO.getProjectBusStatus()) {
                case 2: type = CustomerRemarkEnum.ProjectFinish.getCode(); break;
                case 3: type = CustomerRemarkEnum.ProjectCancel.getCode(); break;
                case 4: type = CustomerRemarkEnum.ProjectFailed.getCode(); break;
            }
            remarkDTO.setType(type);
            remarkService.uAdd(remarkDTO);
        }
        //取消4，取消则直接删除该项目
        if (projectDTO.getProjectBusStatus() == 4) {
            projectMapper.delete(wrapper);
            return JsonData.buildSuccess();
        }
        else {
            projectDO.setProjectBusStatus(projectDTO.getProjectBusStatus());
            projectMapper.update(projectDO, wrapper);
            return JsonData.buildSuccess(projectDO);
        }
    }

    @Override
    public Map<String, Object> uSearch2(int page, int size, int projectBusStatus, String keyWord) {
        Page<CustomerProjectDO> pageInfo = new Page<>(page, size);
        LambdaQueryWrapper<CustomerProjectDO> projectWrapper = new LambdaQueryWrapper<>();
        if (projectBusStatus != -1 && projectBusStatus != 0)
            projectWrapper.eq(CustomerProjectDO::getProjectBusStatus, projectBusStatus);
        else
            projectWrapper.ne(CustomerProjectDO::getProjectBusStatus, -1);
        if (keyWord != null && !keyWord.isEmpty()) {
            //联系人和手机号
            String customerNo = findOneFromCustomerAndGuest(keyWord);
            if (customerNo != null)
                projectWrapper.and(
                        wrapper ->
                                wrapper.like(CustomerProjectDO::getCompanyName, keyWord)
                                        .or()
                                        .eq(CustomerProjectDO::getCustomerNo, customerNo)
                );
            else {
                projectWrapper.like(CustomerProjectDO::getCompanyName, keyWord);
            }
        }
        IPage<CustomerProjectDO> projectDOIPage = projectMapper.selectPage(pageInfo, projectWrapper);
        List<CustomerProjectDTO> projectDTOList = projectDOIPage.getRecords().stream().map(
                DTOUtil::projectDoToDto
        ).collect(Collectors.toList());

        for (CustomerProjectDTO projectDTO: projectDTOList) {
            projectDTO.setCustomer(customerService.getOne(projectDTO.getCustomerNo()));
        }
        Map<String, Object> map = new HashMap<>(3);
        map.put("total_record", projectDOIPage.getTotal());
        map.put("total_page", projectDOIPage.getPages());
        map.put("current_data", projectDTOList);
        return map;
    }

    @Override
    public JsonData uInfo2(String projectId) {
        LambdaQueryWrapper<CustomerProjectDO> wrapper = new LambdaQueryWrapper<>();
        wrapper.eq(CustomerProjectDO::getProjectId, projectId);
        CustomerProjectDO projectDO = projectMapper.selectOne(wrapper);
        CustomerProjectDTO projectDTO = new CustomerProjectDTO();
        if (projectDO == null) {
            return JsonData.buildError("查无此客人");
        }
        BeanUtils.copyProperties(projectDO, projectDTO);
        //项目分析id列表
        projectDTO.setProjectAnalyzeList(
                remarkService.uSearchForList(projectId, CustomerRemarkEnum.ProjectAnalyze.getCode())
        );
        //项目需求id列表
        projectDTO.setProjectRequirementsList(
                remarkService.uSearchForList(projectId, CustomerRemarkEnum.ProjectRequirementRemark.getCode())
        );
        //项目备注id列表
        projectDTO.setProjectRemarkList(
                remarkService.uSearchForList(projectId, CustomerRemarkEnum.ProjectRemark.getCode())
        );
        //销售/业务-策略/方案id列表
        projectDTO.setProjectStrategyList(
                remarkService.uSearchForList(projectId, CustomerRemarkEnum.ProjectStrategy.getCode())
        );
        //销售/业务-计划/实施id列表
        projectDTO.setProjectPlanList(
                remarkService.uSearchForList(projectId, CustomerRemarkEnum.ProjectPlan.getCode())
        );
        return JsonData.buildSuccess(projectDTO);
    }

    @Override
    public void removeByProjectId(String projectId) {
        LambdaQueryWrapper<CustomerProjectDO> wrapper = new LambdaQueryWrapper<>();
        wrapper.eq(CustomerProjectDO::getProjectId, projectId);
        projectMapper.delete(wrapper);
    }


    /**
     * 检测客人信息后再去搜索对应客户信息，最后再来查找相关项目信息
     * @param keyword
     * @return
     */
    private String findOneFromCustomerAndGuest(String keyword) {
        CustomerGuestDO guestDO = guestService.getOne(keyword);
        if (guestDO == null || (guestDO != null && guestDO.getCustomerNo() == null))
            return null;
        CustomerDTO customerDTO = customerService.getOne(keyword);
        if (customerDTO == null)
            return null;
        return customerDTO.getCustomerNo();
    }
}
